home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Software Vault: The Gold Collection
/
Software Vault - The Gold Collection (American Databankers) (1993).ISO
/
cdr10
/
froff.zip
/
FIXCRLF.FOR
< prev
next >
Wrap
Text File
|
1993-01-14
|
27KB
|
738 lines
C RENBR(FIXCRLF/CUT FILE INTO EQUAL LENGTH LINES)
C
C BY DONALD E. BARTH
C
CHARACTER*1 LTRNOW,LTRONE,LTRTWO,LTRLIN(80),CHAR
CHARACTER*80 FILINP,FILOUT
DATA LMTLIN/80/
DATA ITTY,JTTY,IDISK,JDISK/0,0,1,2/
C
C IDENTIFY THIS PROGRAM
WRITE(JTTY,1)
1 FORMAT(' FIXCRLF'/
1' Inserts CRLF after fixed length records.'/
1' Removes nulls and EOFs,',
1' and converts FF or lone CR or LF to CRLF.')
C
C OPEN NEXT INPUT FILE
2 WRITE(JTTY,3)
3 FORMAT(' Input file? ',\)
READ(ITTY,4)FILINP
4 FORMAT(1A80)
IF(FILINP.EQ.' ')GO TO 6
OPEN(UNIT=IDISK,FILE=FILINP,STATUS='OLD',IOSTAT=ICHECK,
1 FORM='BINARY')
IF(ICHECK.EQ.0)GO TO 8
WRITE(JTTY,5)
5 FORMAT(' Cannot open input file')
GO TO 2
6 WRITE(JTTY,7)
7 FORMAT(' Name of input file must be specified')
GO TO 2
8 CONTINUE
C
C OPEN OUTPUT FILE
9 WRITE(JTTY,10)
10 FORMAT(' Output file? ',\)
READ(ITTY,11)FILOUT
11 FORMAT(1A80)
IF(FILOUT.EQ.' ')GO TO 15
OPEN(UNIT=JDISK,FILE=FILOUT,STATUS='OLD',IOSTAT=ICHECK)
IF(ICHECK.NE.0)GO TO 17
CLOSE(UNIT=JDISK)
12 WRITE(JTTY,13)
13 FORMAT(' File already exists. Replace it? ',\)
READ(ITTY,14)LTRNOW
14 FORMAT(1A1)
IF(LTRNOW.EQ.'Y')GO TO 17
IF(LTRNOW.EQ.'y')GO TO 17
IF(LTRNOW.EQ.'N')GO TO 9
IF(LTRNOW.EQ.'n')GO TO 9
GO TO 12
15 WRITE(JTTY,16)
16 FORMAT(' Name of output file must be specified')
GO TO 9
17 OPEN(UNIT=JDISK,FILE=FILOUT,STATUS='NEW',IOSTAT=ICHECK,
1 FORM='BINARY')
IF(ICHECK.EQ.0)GO TO 19
WRITE(JTTY,18)
18 FORMAT(' Cannot open output file')
GO TO 9
19 CONTINUE
C
C ASK LENGTH OF LINES
20 WRITE(JTTY,21)
21 FORMAT(
1' Line length not counting CRLF (0 to only change LF to CRLF)? ',
2\)
READ(ITTY,22)LTRLIN
22 FORMAT(9999A1)
C SUBROUTINE DAHEFT(KONTRL,ITRAIL,IEXTRA,IBUFFR,MAXBFR,
C 1 LOWBFR,KIND ,ISHIFT,JSHIFT,KSHIFT,LSHIFT,IVALUE,
C 2 VALUE )
LOWBFR=1
CALL DAHEFT(0,0,0,LTRLIN,LMTLIN,
1 LOWBFR,KIND,ISHIFT,JSHIFT,KSHIFT,LSHIFT,IVALUE,
2 VALUE )
IF(KIND.NE.3)GO TO 25
IF(IVALUE.LT.0)GO TO 25
23 IF(LOWBFR.GT.LMTLIN)GO TO 24
IF(LTRLIN(LOWBFR).NE.' ')GO TO 25
LOWBFR=LOWBFR+1
GO TO 23
24 GO TO 27
25 WRITE(JTTY,26)
26 FORMAT(
1' Type the length of the lines into',
2' which the file is to be split.'/
3' Do not include the trailing CRLF in this line length.'/
4' Type zero to merely change lone LF characters to CRLF pairs')
GO TO 20
27 LNGLIN=IVALUE
C
C INITIALIZE
C
C KNTINP = NUMBER OF CHARACTERS READ FROM INPUT FILE
C KNTOUT = NUMBER OF CHARACTERS WRITTEN TO OUTPUT FILE
C KNTLIN = NUMBER OF END OF LINES WRITTEN
C IONLIN = LENGTH OF LINE NOW BEING OUTPUT
C NEWLIN = NUMBER OF END OF LINES STILL TO BE OUTPUT
C KNTCR = NUMBER OF CARRIAGE RETURNS NOT YET OUTPUT
C KNTLF = NUMBER OF LINE FEEDS NOT YET OUTPUT
C MSTLIN = LENGTH OF LONGEST OUTPUT LINE
C
KNTINP=0
KNTOUT=0
KNTLIN=0
IONLIN=0
NEWLIN=0
KNTCR=0
KNTLF=0
MSTLIN=0
KNTNUL=0
KNTEOF=0
C
C COPY THE FILE, INSERTING END OF LINES AS NEEDED
28 READ(IDISK,END=33)LTRONE
KNTINP=KNTINP+1
KODE=ICHAR(LTRONE)
IF(KODE.EQ.0)GO TO 40
IF(KODE.EQ.10)GO TO 31
IF(KODE.EQ.12)GO TO 31
IF(KODE.EQ.13)GO TO 32
IF(KODE.EQ.26)GO TO 426
IF(NEWLIN.NE.0)GO TO 29
IF(LNGLIN.LE.0)GO TO 30
IF(IONLIN.LT.LNGLIN)GO TO 30
C
C INSERT CR = 13 LF = 10 AT START OF NEW LINE
29 LTRTWO=CHAR(13)
WRITE(JDISK)LTRTWO
LTRTWO=CHAR(10)
WRITE(JDISK)LTRTWO
KNTOUT=KNTOUT+2
NEWLIN=NEWLIN-1
KNTLIN=KNTLIN+1
CALL RUNLIN(KNTLIN,ITTY,JTTY)
IF(NEWLIN.GT.0)GO TO 29
KNTCR=0
KNTLF=0
NEWLIN=0
IONLIN=0
C
C OUTPUT THE SINGLE NEW CHARACTER
30 KNTOUT=KNTOUT+1
IONLIN=IONLIN+1
WRITE(JDISK)LTRONE
IF(MSTLIN.LT.IONLIN)MSTLIN=IONLIN
GO TO 28
C
C LINE FEED (10) OR FORM FEED (12)
31 KNTLF=KNTLF+1
NEWLIN=KNTLF
IF(NEWLIN.LT.KNTCR)NEWLIN=KNTCR
GO TO 28
C
C CARRIAGE RETURN (13)
32 KNTCR=KNTCR+1
NEWLIN=KNTLF
IF(NEWLIN.LT.KNTCR)NEWLIN=KNTCR
GO TO 28
C
C NULL (0)
40 KNTNUL=KNTNUL+1
GO TO 28
C
C END OF FILE (26)
426 KNTEOF=KNTEOF+1
GO TO 28
C
C INSERT CR = 13 LF = 10 AT END OF FILE
33 IF(NEWLIN.NE.0)GO TO 34
IF(IONLIN.EQ.0)GO TO 35
34 LTRTWO=CHAR(13)
WRITE(JDISK)LTRTWO
LTRTWO=CHAR(10)
WRITE(JDISK)LTRTWO
KNTOUT=KNTOUT+2
NEWLIN=NEWLIN-1
KNTLIN=KNTLIN+1
CALL RUNLIN(KNTLIN,ITTY,JTTY)
IF(NEWLIN.GT.0)GO TO 34
35 CONTINUE
C
C ALL DONE
WRITE(JTTY,36)KNTINP
WRITE(JTTY,37)KNTOUT
WRITE(JTTY,38)KNTLIN
WRITE(JTTY,39)MSTLIN
WRITE(JTTY,41)KNTNUL
WRITE(JTTY,526)KNTEOF
36 FORMAT(' ',1I10,' bytes read')
37 FORMAT(' ',1I10,' bytes written')
38 FORMAT(' ',1I10,' lines written')
39 FORMAT(' ',1I10,' length of longest output line')
41 FORMAT(' ',1I10,' null characters removed')
526 FORMAT(' ',1I10,' EOF characters removed')
C
C ALL DONE
END
SUBROUTINE RUNLIN(LINE,ITTY,JTTY)
IF(LINE.EQ.1)WRITE(JTTY,1)LINE
IF(LINE.GT. 1.AND.LINE.LT. 10)WRITE(JTTY,2)LINE
IF(LINE.GE. 10.AND.LINE.LT. 100)WRITE(JTTY,3)LINE
IF(LINE.GE. 100.AND.LINE.LT. 1000)WRITE(JTTY,4)LINE
IF(LINE.GE. 1000.AND.LINE.LT. 10000)WRITE(JTTY,5)LINE
IF(LINE.GE. 10000.AND.LINE.LT. 100000)WRITE(JTTY,6)LINE
IF(LINE.GE. 100000.AND.LINE.LT. 1000000)WRITE(JTTY,7)LINE
IF(LINE.GE. 1000000.AND.LINE.LT. 10000000)WRITE(JTTY,8)LINE
IF(LINE.GE. 10000000.AND.LINE.LT. 100000000)WRITE(JTTY,9)LINE
IF(LINE.GE.100000000.AND.LINE.LT.1000000000)WRITE(JTTY,10)LINE
C 123456789 1234567890
1 FORMAT(' ',1I1)
2 FORMAT('+',1I1)
3 FORMAT('+',1I2)
4 FORMAT('+',1I3)
5 FORMAT('+',1I4)
6 FORMAT('+',1I5)
7 FORMAT('+',1I6)
8 FORMAT('+',1I7)
9 FORMAT('+',1I8)
10 FORMAT('+',1I9)
RETURN
END
SUBROUTINE DAHEFT(KONTRL,ITRAIL,IEXTRA,IBUFFR,MAXBFR,
1 LOWBFR,KIND ,ISHIFT,JSHIFT,KSHIFT,LSHIFT,IVALUE,
2 VALUE )
C RENBR(/FREE FORMAT NUMERIC INPUT ROUTINE)
C
C DONALD BARTH, HARVARD BUSINESS SCHOOL
C
C DAHEFT INTERPRETS AN ARRAY READ BY THE CALLING
C PROGRAM WITH A MULTIPLE OF AN A1 FORMAT AND RETURNS
C THE VALUES CONTAINED IN THIS ARRAY.
C
C NUMBERS INTERPRETTED BY DAHEFT CAN CONTAIN LEADING
C SIGN, EMBEDDED DECIMAL POINT AND/OR TRAILING E WITH
C SIGNED EXPONENT. A PERCENT SIGN FOLLOWING THE NUMBER
C IMPLIES E-2, TRAILING LETTER K IMPLIES E3 AND
C TRAILING LETTER M IMPLIES E6.
C
C ARGUMENT LIST DEFINITIONS:
C
C KONTRL = 1 OR GREATER, ITEM IN IBUFFR ARRAY IS
C FLOATING POINT. IF POSSIBLE, THE FLOATING
C POINT NUMBER WILL BE ACCUMULATED AS AN
C INTEGER, THEN BE CONVERTED TO FLOATING POINT
C AND SHIFTED IF NECESSARY. KONTRL IS THEN
C THE MAXIMUM NUMBER OF DIGITS IN THE INTEGER.
C THE VALUE IS OUTPUT AS THE ARGUMENT VALUE.
C IF THE ITEM HAS MORE THAN KONTRL DIGITS,
C THEN THE ENTIRE EVALUATION IS DONE IN
C FLOATING POINT. THE ADVANTAGE OF
C CALCULATING THE FLOATING POINT VALUES IN
C INTEGER AS LONG AS THE PRECISION OF THE
C COMPUTER IS NOT OVERFLOWED IS THAT THE
C CALCULATION OF THE PORTION OF THE NUMBER
C RIGHT OF THE DECIMAL POINT IS MORE EXACT.
C AS AN EXAMPLE, IF KONTRL IS GREATER THAN OR
C EQUAL TO 4, THEN THE NUMBER 33.33 CAN BE
C STORED AS THE INTEGER 3333, THEN BE
C CONVERTED TO FLOATING POINT VALUE 3333.0 AND
C DIVIDED BY 100.0 TO OBTAIN THE FINAL
C ANSWER. IF IT MAKES NO DIFFERENCE WHETHER
C THE NUMBER TYPED AS 33.33 HAS VALUE 33.33 OR
C 33.32999... THEN KONTRL CAN BE GIVEN THE
C VALUE 1.
C = 0, ITEM IN IBUFFR ARRAY IS INTEGER DECIMAL.
C THE NUMBER CAN BE TYPED WITH A DECIMAL POINT
C (FOR EXAMPLE 1.23K OR 1.23E3 EQUALS 1230),
C BUT IS STORED AS AN INTEGER IN DAHEFT, AND
C IS OUTPUT AS ARGUMENT IVALUE. ANY DECIMAL
C INTEGER WHICH THE COMPUTER CAN REPRESENT CAN
C BE EVALUATED. THIS INCLUDES, ON TWOS
C COMPLEMENT COMPUTERS, THE LARGEST NEGATIVE
C NUMBER THE ABSOLUTE VALUE OF WHICH CANNOT BE
C STORED. ON THE PDP10, A 36 BIT COMPUTER
C WITH TWOS COMPLEMENT NOTATION, THE RANGE OF
C DECIMAL INTEGERS IS -34359738368 THROUGH
C 34359738367 (OCTAL NOTATION OF BIT PATTERNS
C BEING 400000000000 THROUGH 377777777777).
C = -1, ITEM IN IBUFFR ARRAY IS OCTAL. THE
C NUMBER CAN BE TYPED WITH A DECIMAL POINT
C AND/OR WITH AN EXPONENT. HOWEVER, THE
C NUMBER FOLLOWING THE LETTER E OF THE
C EXPONENT IS EVALUATED IN DECIMAL. THE VALUE
C OF THE OCTAL NUMBER IS RETURNED AS THE
C ARGUMENT IVALUE. IT MUST BE NOTED THAT
C NUMBERS EVALUATED AS NEGATIVE OCTAL INTEGERS
C HAVE THE NEGATIVE OCTAL INTEGER AS THEIR
C VALUE, NOT AS THEIR BIT REPRESENTATION IN
C COMPUTER STORAGE. FOR EXAMPLE, ON A 36 BIT
C TWOS COMPLEMENT COMPUTER, THE OCTAL NUMBER
C -400000000000 (WHICH COULD ALSO BE TYPED AS
C -4E11 OR -4E+11 WHERE THE 11 AFTER THE E IS
C IN DECIMAL) IS REPRESENTED AS BIT PATTERN
C HAVING OCTAL NOTATION 400000000000 AND THE
C OCTAL NUMBER -377777777777 IS REPRESENTED BY
C THE BIT PATTERN 400000000001.
C = -2, DO NOT EVALUATE NUMBERS. INSTEAD THE
C CHARACTERS FORMING NUMBER ARE TREATED LIKE
C ANY OTHER PRINTING CHARACTERS.
C ITRAIL = SPECIFIES WHETHER EXPONENTS ARE TO BE
C RECOGNIZED.
C = -1, ALLOW NUMBERS TO BE FOLLOWED BY E
C EXPONENT, BUT DO NOT RECOGNIZE PERCENT SIGN,
C K OR M AT END OF NUMBER. E IS NOT
C RECOGNIZED IF NOT PRECEDED BY SIGN, DECIMAL
C POINT OR DIGIT.
C = 0, DO NOT ALLOW TRAILING PERCENT SIGN, K M
C OR E EXPONENT.
C = 1, ALLOW NUMBERS TO BE FOLLOWED BY PERCENT
C SIGN, K M OR E EXPONENT. PERCENT SIGN, K M
C OR E IS NOT RECOGNIZED IF NOT PRECEDED BY
C SIGN, DECIMAL POINT OR DIGIT.
C
C FOLLOWING VALUES DO NOT REQUIRE THAT EXPONENT
C BE PRECEDED BY NUMBER. ALTHOUGH RETURNED
C VALUE WILL ALWAYS BE ZERO IF NO VALUE DIGITS
C ARE FOUND, CALLING PROGRAM COULD ADJUST THIS
C RETURNED VALUE.
C
C = -3, LEADING E EXPONENT IS RECOGNIZED.
C LEADING DIGITS, SIGNS AND DECIMAL POINTS ARE
C NOT ALLOWED.
C = -2, SAME AS ITRAIL=-1, EXCEPT THAT IN
C ADDITION E EXPONENT IS RECOGNIZED EVEN IF
C NOT PRECEDED BY DIGITS, SIGN OR DECIMAL
C POINT.
C = 2, SAME AS ITRAIL=1, EXCEPT THAT IN ADDITION
C LEADING PERCENT SIGN, OR LETTERS K M OR E
C EXPONENT ARE RECOGNIZED EVEN IF NOT PRECEDED
C BY DIGITS, SIGN OR DECIMAL POINT.
C = 3, ONLY LEADING PERCENT SIGN OR LETTERS K M
C OR E EXPONENT ARE RECOGNIZED. LEADING
C DIGITS, SIGNS OR DECIMAL POINTS ARE NOT
C ALLOWED.
C
C IF 10 IS SUBTRACTED FROM ITRAIL VALUES -3
C THROUGH 3, AND IF EITHER VALUE DIGITS OR
C DIGITS FOLLOWING LETTER E ARE MISSING, THEN
C ONE, RATHER THAN ZERO, IS ASSUMED TO BE THE
C DEFAULT FOR THE VALUE OR THE EXPONENT
C RESPECTIVELY. -E- WOULD BE EQUIVALENT TO
C -1E-1 AND -E OR -E+ WOULD BE EQUIVALENT TO
C -1E1
C
C IF 10 IS ADDED TO ITRAIL VALUES -3 THROUGH 3,
C THEN VALUE IS RETURNED AS THOUGH NEITHER
C EXPONENT NOR DECIMAL POINT HAD BEEN TYPED.
C VALUE INDICATED BY COMBINATION OF DIGITS,
C DECIMAL POINT AND/OR EXPONENT CAN BE OBTAINED
C AS VALUE*10**KSHIFT OR IVALUE*10**KSHIFT.
C VALUE INDICATED BY COMBINATION OF DIGITS AND
C DECIMAL POINT BUT IGNORING EXPONENT CAN BE
C OBTAINED AS VALUE*10**(KSHIFT-JSHIFT) OR
C IVALUE*10**(KSHIFT-JSHIFT).
C IEXTRA = EXTRA SHIFT TO BE APPLIED TO VALUE. SHIFT
C IS STATED AS POWER OF RADIX. THIS IS
C APPLIED IN ADDITION TO SHIFT REPORTED IN
C ISHIFT, JSHIFT AND KSHIFT AS SPECIFIED BY
C USER. FOR EXAMPLE, IF DOLLAR VALUE IS TO BE
C RETURNED AS INTEGER NUMBER OF CENTS, IEXTRA
C WOULD HAVE VALUE 2.
C IBUFFR = INPUT BUFFER ARRAY CONTAINING CHARACTERS
C TYPED BY USER, READ BY A MULTIPLE OF AN A1
C FORMAT, WHICH IS TO BE SEARCHED FOR WORDS
C AND NUMBERS. IBUFFR THEN CONTAINS 1 LETTER
C PER COMPUTER STORAGE LOCATION.
C MAXBFR = MAXIMUM SUBSCRIPT OF IBUFFR ARRAY TO BE
C SEARCHED
C LOWBFR = SUBSCRIPT WITHIN THE IBUFFR ARRAY OF THE
C FIRST (LEFTMOST) CHARACTER WHICH CAN BE
C SCANNED FOR NUMBERS. LOWBFR WILL BE RETURNED
C POINTING TO FIRST PRINTING CHARACTER WHICH
C CANNOT APPEAR IN A NUMBER, OR BEYOND THE END
C OF THE BUFFER IF THE BUFFER DOES NOT CONTAIN
C ANY PRINTING CHARACTERS.
C KIND = RETURNED DESCRIBING THE KIND OF ITEM LOCATED
C IN THE IBUFFR ARRAY.
C = 1, NOTHING WAS FOUND AT OR TO THE RIGHT OF
C LOWBFR. THE CALLING PROGRAM SHOULD READ A
C NEW LINE INTO IBUFFR.
C = 2, NUMBER WAS NOT FOUND, BUT A PRINTING
C CHARACTER WHICH CANNOT START A NUMBER WAS
C FOUND. LOWBFR IS RETURNED POINTING TO THIS
C PRINTING CHARACTER.
C = 3, A NUMBER WAS FOUND. LOWBFR IS RETURNED
C POINTING TO CHARACTER TO RIGHT OF NUMBER.
C ISHIFT = 0, RETURNED IF NONE OF CHARACTERS E, %, K OR
C M FOLLOW NUMBER
C = 1, PERCENT SIGN FOLLOWS NUMBER
C = 2, K FOLLOWS NUMBER
C = 3, M FOLLOWS NUMBER
C = LESS THAN ZERO, RETURNED IF E FOLLOWS
C NUMBER.
C = -1, E AND POSSIBLY SIGNED NUMBER FOLLOW
C NUMBER.
C = -2, E IS FOLLOWED BY PLUS SIGN NOT IN TURN
C FOLLOWED BY DIGITS.
C = -3, E IS FOLLOWED BY MINUS SIGN NOT IN TURN
C FOLLOWED BY DIGITS.
C = -4, E IS FOLLOWED BY NEITHER SIGN NOR DIGITS
C JSHIFT = EXPONENT INDICATED BY FOLLOWING PERCENT
C SIGN, K, M OR E FOLLOWED BY DIGITS. THIS
C WILL HAVE BEEN APPLIED TO RETURNED VALUE IF
C ITRAIL EQUALS EITHER -1 OR 1. 12.34K OR
C 12.34E3 WOULD GIVE JSHIFT OF 3. 12% OR
C 12E-2 WOULD GIVE JSHIFT -2.
C KSHIFT = EXPONENT WHICH WOULD BE NECESSARY TO OBTAIN
C DESIRED VALUE IF NUMBER HAD BEEN TYPED
C WITHOUT DECIMAL POINT. 12.34 STATED WITHOUT
C DECIMAL POINT WOULD BE 1234E-2 SO KSHIFT
C WOULD BE -2. 12.34K WOULD BE 1234E1 SO
C KSHIFT WOULD BE 1.
C LSHIFT = ZERO OR LESS, THE VALUE ZERO IS BEING
C RETURNED FOR EITHER VALUE OR IVALUE,
C WHICHEVER IS APPROPRIATE.
C = -4, NUMBER CONTAINED NEITHER VALUE DIGITS,
C NOR DECIMAL POINT, NOR LEADING PLUS SIGN,
C NOR LEADING MINUS SIGN. THIS VALUE OF
C LSHIFT IS ALWAYS RETURNED IF KIND IS
C RETURNED CONTAINING A VALUE OTHER THAN 3.
C IF KIND IS RETURNED CONTAINING THE VALUE 3,
C THEN ITRAIL MUST BE EITHER -3 OR 3, AND THE
C CONTENTS OF THE INPUT TEXT BUFFER MUST BEGIN
C WITH A REPRESENTATION OF AN EXPONENT.
C = -3, A LEADING MINUS SIGN BUT NO VALUE DIGITS
C WAS FOUND.
C = -2, A LEADING PLUS SIGN BUT NO VALUE DIGITS
C WAS FOUND.
C = -1, A LEADING PERIOD BUT NO VALUE DIGITS WAS
C FOUND.
C = 0, ONE OR MORE ZERO DIGITS WERE FOUND, BUT
C THE NUMBER CONTAINED NO DIGITS OTHER THAN
C ZERO. THE NUMBER REPRESENTATION MAY OR MAY
C NOT HAVE BEEN BEGUN BY A PLUS SIGN OR A
C MINUS SIGN AND MAY OR MAY NOT HAVE CONTAINED
C A DECIMAL POINT.
C = GREATER THAN ZERO, LSHIFT IS NUMBER OF
C DIGITS COUNTING LEFTMOST NON-ZERO DIGIT AND
C ALL WHICH WERE SPECIFIED TO ITS RIGHT. THIS
C IS INDEPENDENT OF ANY SHIFT IMPLIED BY A
C DECIMAL POINT OR EXPONENT
C IVALUE = RETURNED WITH VALUE IF KONTRL IS LESS THAN
C OR EQUAL TO ZERO. NOTE THAT IF KONTRL IS
C LESS THAN OR EQUAL TO ZERO, THEN ORIGINAL
C CONTENT OF IVALUE IS ALWAYS DESTROYED. IN
C PARTICULAR, IF KONTRL IS LESS THAN OR EQUAL
C TO ZERO AND IF KIND IS RETURNED CONTAINING
C EITHER 1 OR 2, THEN IVALUE WILL BE ZEROED.
C VALUE = RETURNED WITH VALUE IF KONTRL IS GREATER
C THAN ZERO. NOTE THAT IF KONTRL IS GREATER
C THAN ZERO, THEN THE ORIGINAL CONTENT OF
C VALUE IS ALWAYS DESTROYED. IN PARTICULAR,
C IF KONTRL IS GREATER THAN ZERO AND IF KIND
C IS RETURNED CONTAINING EITHER 1 OR 2, THEN
C VALUE WILL BE ZEROED.
C
CHARACTER*1 IBUFFR(MAXBFR),IDIGIT(10),KAPLTR(3),
1LOWLTR(3)
C
DIMENSION JPOWER(3)
C
CHARACTER*1 IPLUS,IMINUS,IDOT,IBLANK,ITAB,NOWLTR,
1 KAPEXP,LOWEXP
C
C IDIGIT CONTAINS ALPHAMERIC FORM OF DIGITS 0 THRU 9
DATA IDIGIT/'0','1','2','3','4','5','6','7','8','9'/
C
C IBLANK CONTAINS SPACE CHARACTER AND ITAB CONTAINS
C TAB CHARACTER. IF TAB CHARACTER IS NOT AVAILABLE,
C ITAB SHOULD INSTEAD CONTAIN A SPACE ALSO.
C
DATA IPLUS,IMINUS,IDOT,IBLANK,ITAB/
1'+','-','.',' ',' '/
C
C KAPLTR = LIST OF UPPER CASE LETTERS WHICH CAN FOLLOW
C A NUMBER TO INDICATE AN EXPONENT.
C LOWLTR = LIST OF LOWER CASE LETTERS CORRESPONDING TO
C UPPER CASE LETTERS IN KAPLTR ARRAY.
C JPOWER = VALUE OF THE EXPONENT ASSOCIATED WITH THE
C PARALLEL CHARACTERS IN THE KAPLTR AND LOWLTR
C ARRAYS. JPOWER CAN BE NEGATIVE, FOR EXAMPLE
C PERCENT SIGN WOULD CORRESPOND TO JPOWER=-2.
C MAXTST = NUMBER OF ITEMS IN EACH OF KAPLTR, LOWLTR
C AND JPOWER ARRAYS.
C KAPEXP = UPPER CASE LETTER E
C LOWEXP = LOWER CASE LETTER E
C
C UPPER CASE LETTERS CAN BE SUBSTITUTED FOR LOWER CASE
C IN FOLLOWING DATA STATEMENTS, IF COMPUTER UPON WHICH
C THIS ROUTINE IS USED DOES NOT SUPPORT LOWER CASE.
C
DATA KAPLTR/'%','K','M'/
DATA LOWLTR/'%','k','m'/
DATA JPOWER/-2,3,6/
DATA MAXTST/3/
DATA KAPEXP,LOWEXP/'E','e'/
C
C INITIALIZE
ISIGN=0
IF(KONTRL.GT.0)VALUE=0.0
IF(KONTRL.LE.0)IVALUE=0
ISHIFT=0
JSHIFT=0
KSHIFT=0
LSHIFT=-4
IRADIX=10
IF(KONTRL.LT.0)IRADIX=8
IADD=IRADIX-2
IPOWER=0
NUMKNT=-4
NUMVAL=0
NMBEXP=-1
NUMPNT=-1
IDEFLT=0
IF(ITRAIL.LT.-5)IDEFLT=1
KTRAIL=ITRAIL
IF(KTRAIL.GT.5)KTRAIL=KTRAIL-10
IF(KTRAIL.LT.-5)KTRAIL=KTRAIL+10
LTRAIL=KTRAIL
IF(LTRAIL.LT.0)LTRAIL=-LTRAIL
GO TO 2
C
C *********************
C * SCAN FOR NUMBER *
C *********************
C
C LOOP LOOKING AT CHARACTERS IN IBUFFR ARRAY
1 LOWBFR=LOWBFR+1
2 IF(LOWBFR.GT.MAXBFR)GO TO 25
NOWLTR=IBUFFR(LOWBFR)
IF(NMBEXP.GE.0)GO TO 20
IF(ISIGN.NE.0)GO TO 4
C
C SCAN OVER LEADING SPACES AND/OR TABS
IF(NOWLTR.EQ.IBLANK)GO TO 1
IF(NOWLTR.EQ.ITAB)GO TO 1
C
C LOOK FOR INITIAL SIGNS + OR -
IF(KONTRL.LE.-2)GO TO 40
IF(LTRAIL.GE.3)GO TO 4
IF(NOWLTR.EQ.IPLUS)GO TO 3
IF(NOWLTR.NE.IMINUS)GO TO 4
ISIGN=-1
NUMKNT=-3
GO TO 1
3 ISIGN=1
NUMKNT=-2
GO TO 1
C
C LOOK FOR % K OR M FOLLOWING NUMBER
C LOCK OUT THESE AND ALSO E IF NO PART OF NUMBER FOUND
4 IF(LTRAIL.GE.2)GO TO 5
IF(ISIGN.EQ.0)GO TO 10
IF(KTRAIL.EQ.0)GO TO 10
5 IF(KTRAIL.LT.0)GO TO 8
I=0
6 I=I+1
IF(I.GT.MAXTST)GO TO 8
IF(NOWLTR.EQ.KAPLTR(I))GO TO 7
IF(NOWLTR.NE.LOWLTR(I))GO TO 6
7 IPOWER=JPOWER(I)
JSIGN=1
NMBEXP=1
ISHIFT=I
LOWBFR=LOWBFR+1
GO TO 26
C
C LOOK FOR LETTER E
8 IF(NOWLTR.EQ.KAPEXP)GO TO 9
IF(NOWLTR.NE.LOWEXP)GO TO 10
9 JSIGN=0
NMBEXP=0
ISHIFT=-4
GO TO 19
C
C LOOK FOR LEADING OR EMBEDDED PERIOD
10 IF(LTRAIL.GE.3)GO TO 24
IF(NUMPNT.GE.0)GO TO 11
IF(NOWLTR.NE.IDOT)GO TO 11
DECML=0.1
IF(ISIGN.EQ.0)NUMKNT=-1
GO TO 18
C
C LOOK FOR DIGIT OTHER THAN IN EXPONENT FIELD
11 DO 16 I=1,IRADIX
IF(NOWLTR.NE.IDIGIT(I))GO TO 16
IF(NUMKNT.GT.0)GO TO 12
NUMKNT=0
IF(I.EQ.1)GO TO 13
12 NUMKNT=NUMKNT+1
13 IF(KONTRL.LE.0)GO TO 15
IF(NUMKNT.LE.KONTRL)NUMVAL=(10*NUMVAL)+I-1
IF(NUMPNT.GE.0)GO TO 14
VALUE=(10.0*VALUE)+FLOAT(I-1)
GO TO 19
14 VALUE=VALUE+(DECML*FLOAT(I-1))
DECML=DECML/10.0
GO TO 18
C FOLLOWING ALLOWS LARGEST NEGATIVE NUMBER FOR
C WHICH THERE IS NOT CORRESPONDING POSITIVE VALUE
15 IF(NUMKNT.EQ.1)IVALUE=I-2
IF(NUMKNT.GT.1)IVALUE=(IRADIX*IVALUE)+I+IADD
GO TO 17
16 CONTINUE
GO TO 24
C
C DIGIT, E OR . FOUND SO MARK AS BEING IN NUMBER
17 IF(NUMPNT.LT.0)GO TO 19
18 NUMPNT=NUMPNT+1
19 IF(ISIGN.EQ.0)ISIGN=1
GO TO 1
C
C LOOK FOR SIGN IN EXPONENT FIELD
20 IF(JSIGN.NE.0)GO TO 22
IF(NOWLTR.EQ.IPLUS)GO TO 21
IF(NOWLTR.NE.IMINUS)GO TO 22
JSIGN=-1
ISHIFT=-3
GO TO 1
21 JSIGN=1
ISHIFT=-2
GO TO 1
C
C LOOK FOR DIGITS IN EXPONENT FIELD
22 DO 23 I=1,10
IF(NOWLTR.NE.IDIGIT(I))GO TO 23
IPOWER=(10*IPOWER)+I-1
NMBEXP=1
ISHIFT=-1
IF(JSIGN.EQ.0)JSIGN=1
GO TO 1
23 CONTINUE
GO TO 26
C
C DECIDE WHAT TO DO IF NO MATCH FOUND
24 IF(ISIGN.NE.0)GO TO 26
GO TO 40
C
C *******************************
C * NUMBER HAS BEEN EVALUATED *
C *******************************
C
25 IF(ISIGN.EQ.0)GO TO 39
26 KIND=3
C
C ADJUST EXPONENT SIGN
IF(NMBEXP.LT.0)GO TO 27
IF(NMBEXP.EQ.0)IPOWER=IDEFLT
IF(JSIGN.LT.0)IPOWER=-IPOWER
C
C SHIFT FLOATING POINT NUMBER ACCORDING TO EXPONENT
27 JSHIFT=IPOWER
KSHIFT=IPOWER
IF(NUMPNT.GT.0)KSHIFT=KSHIFT-NUMPNT
LSHIFT=NUMKNT
IF(NUMPNT.LT.0)NUMPNT=0
IF(ITRAIL.GT.5)IPOWER=NUMPNT
IPOWER=IPOWER+IEXTRA
IF(KONTRL.LE.0)GO TO 31
IF(NUMKNT.GT.KONTRL)GO TO 28
IF(NUMKNT.LT.0)NUMVAL=IDEFLT
IF(ISIGN.LT.0)NUMVAL=-NUMVAL
VALUE=FLOAT(NUMVAL)
IPOWER=IPOWER-NUMPNT
GO TO 29
28 IF(NUMKNT.LT.0)VALUE=IDEFLT
IF(ISIGN.LT.0)VALUE=-VALUE
29 IF(IPOWER.EQ.0)GO TO 41
IF(IPOWER.GT.0)GO TO 30
IPOWER=-IPOWER
VALUE=VALUE/(10.0**IPOWER)
GO TO 41
30 VALUE=VALUE*(10.0**IPOWER)
GO TO 41
C
C SHIFT AN INTEGER ACCORDING TO EXPONENT
31 IF(NUMKNT.LT.0)IVALUE=IDEFLT
IPOWER=IPOWER-NUMPNT
IF(ISIGN.GE.0)GO TO 32
IVALUE=-IVALUE
C NOTE THAT NEGATIVE NUMBER AT THIS POINT HAS ABSOLUTE
C VALUE 1 TOO LOW TO ALLOW THE LARGEST NEGATIVE NUMBER
C WHICH HAS NO CORRESPONDING POSITIVE VALUE IN TWOS
C COMPLEMENT NOTATION
IF(NUMKNT.GT.0)IVALUE=IVALUE-1
GO TO 33
32 IF(NUMKNT.GT.0)IVALUE=IVALUE+1
33 IF(IPOWER.LE.0)GO TO 37
IPOWER=IPOWER-1
KVALUE=IVALUE
IVALUE=IRADIX*IVALUE
IF(ISIGN.GE.0)GO TO 34
IF(IVALUE.GE.KVALUE)GO TO 36
GO TO 35
34 IF(IVALUE.LE.KVALUE)GO TO 36
35 IF((IVALUE/IRADIX).EQ.KVALUE)GO TO 33
36 IVALUE=KVALUE
37 IF(IPOWER.GE.0)GO TO 41
IPOWER=IPOWER+1
KVALUE=IVALUE
IVALUE=IVALUE/IRADIX
IF(ISIGN.GE.0)GO TO 38
IF((IRADIX*IVALUE).LT.KVALUE)IVALUE=IVALUE+1
38 IF(IVALUE.NE.0)GO TO 37
GO TO 41
C
C NUMBER NOT FOUND
39 KIND=1
GO TO 41
40 KIND=2
C
C RETURN TO CALLING PROGRAM
41 RETURN
C
C IBLANK = THE BLANK OR SPACE CHARACTER
C JSIGN = 0, NEITHER SIGN NOR DIGITS AFTER E
C = 1, EITHER PLUS OR DIGITS AFTER E
C = -1, MINUS SIGN AFTER E
C ITAB = THE TAB CHARACTER
C ISIGN = 0, NO PART OF NUMBER ENCOUNTERED
C = -1, MINUS SIGN AT START OF NUMBER
C = 1, NUMBER DOES NOT START WITH MINUS SIGN
C NMBEXP = -1, NO EXPONENT FIELD YET FOUND
C = 0, EXPONENT FIELD FOUND BUT NUMBER NOT
C YET FOUND
C = 1, NUMBER FOUND IN EXPONENT FIELD
C NOWLTR = THE CHARACTER CURRENTLY BEING TESTED
C NUMKNT = NUMBER OF DIGITS IN VALUE FIELD
C = 0, LEFT HAND ZERO ONLY READ SO FAR
C = -1, NO DIGITS YET FOUND
C NUMPNT = -1, DECIMAL POINT NOT YET FOUND
C = 0, DECIMAL POINT ENCOUNTERED IN VALUE FIELD
C = .GT.0, VALUE IS NUMBER OF DIGITS ENCOUNTERED
C TO RIGHT OF DECIMAL POINT IN NUMBER.
END